﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.IO;

namespace ImageComparison
{
    public partial class Form1 : Form
    {

        /*TODO
         * Colour Histogram
         * http://en.wikipedia.org/wiki/Color_histogram
         * Using the results of this to check how close the shadings can be to each other
         * Will have to be a combined result as the image could be upside down and still
         * have the same histogram results
         * 
         * 10x10 Grid feature
         * 
         * Light and shading     
         */

        public Form1()
        {
            InitializeComponent();
        }

        private void btnName_Click(object sender, EventArgs e)
        {
            string image1Name, image2Name;
            image1Name = txtImage1.Text;
            image2Name = txtImage2.Text;


            Bitmap image1 = new Bitmap(image1Name);
            Bitmap image2 = new Bitmap(image2Name);

            //Static declaration of images
            //Bitmap image1 = new Bitmap("C:\\Users\\Etienne\\Desktop\\3.jpg");
            //Bitmap image2 = new Bitmap("C:\\Users\\Etienne\\Desktop\\4.jpg");
            double Percentage;

            Percentage = Compare(image1,image2);
            MessageBox.Show("Percentage similar: " + Percentage.ToString() + "%", "Percentage Compare", MessageBoxButtons.OK,MessageBoxIcon.Information);
            //MessageBox.Show(Percentage.ToString());

        }

        public Double Compare(Image img1_, Image img2_)
        {
            //total number of pixels
            int pixelNb = img1_.Width * img1_.Height;

            Double percent = 100;

            Bitmap resized_img2_ = ResizeBitmap((Bitmap)img2_, img1_.Width, img1_.Height);

            for (int i = 0; i < img1_.Width; i++)
            {
                for (int j = 0; j < img1_.Height; j++)
                {
                    percent -= ColorCompare(((Bitmap)img1_).GetPixel(i, j), ((Bitmap)resized_img2_).GetPixel(i, j)) / pixelNb;
                }
            }

            return percent;
        }

        public Bitmap ResizeBitmap(Bitmap b, int nWidth, int nHeight)
        {
            Bitmap result = new Bitmap(nWidth, nHeight);
            using (Graphics g = Graphics.FromImage((Image)result))
                g.DrawImage(b, 0, 0, nWidth, nHeight);
            return result;
        }

        public Double ColorCompare(Color c1, Color c2)
        {
            return Double.Parse((Math.Abs(c1.B - c2.B) + Math.Abs(c1.R - c2.R) + Math.Abs(c1.G - c2.G)).ToString()) * 100 / (3 * 255);
        }



        private void button2_Click(object sender, EventArgs e)
        {
            ImageDialog2.ShowDialog();
            txtImage2.Text = ImageDialog2.FileName;
        }

        private void btnHistogram_Click(object sender, EventArgs e)
        {
            Double percent;

            string image1Name, image2Name;
            image1Name = txtImage1.Text;
            image2Name = txtImage2.Text;


            Bitmap image1 = new Bitmap(image1Name);
            Bitmap image2 = new Bitmap(image2Name);

            percent = ColourHistogramCompare(image1, image2);

            MessageBox.Show("Percentage similar: " + percent.ToString() + "%", "Percentage Compare", MessageBoxButtons.OK, MessageBoxIcon.Information);

        }

        public Double ColourHistogramCompare(Image img1_, Image img2_)
        {
            Double percent = 100;
            Int32[] image1Grid;
            Int32[] image2Grid;

            image1Grid = new int[64];
            image2Grid = new int[64];

            string image1Name, image2Name;
            image1Name = txtImage1.Text;
            image2Name = txtImage2.Text;


            Bitmap image1 = new Bitmap(image1Name);
            Bitmap image2 = new Bitmap(image2Name);

            image1Grid = BuildHistogramGrid(image1);
            image2Grid = BuildHistogramGrid(image2);

            percent = CalculateHistogramComparison(image1Grid, image2Grid);

            return percent;

        }


        public Int32[] BuildHistogramGrid(Image img1_)
        {
            Int32[] Grid;

            Grid = new int[64];


            for (int i = 0; i < img1_.Width; i++)
            {
                for (int j = 0; j < img1_.Height; j++)
                {                    
                    CheckBin(((Bitmap)img1_).GetPixel(i, j), Grid);
                }
            }

            return Grid;

        }


        public void CheckBin(Color c1, Int32[] RGBColour)
        {

            //Int32[] RGBColour;
            //RGBColour = new Int32[64];

            //for (int i = 0; i < RGBColour.Length; i++)
            //{
            //    RGBColour[i] = 0;
            //}

            //First part of the red checking
            if (c1.R >= 0  && c1.R <= 63)
            {
                if (c1.G >= 0 && c1.G <= 63)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[0] = RGBColour[0] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[1] = RGBColour[1] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[2] = RGBColour[2] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[3] = RGBColour[3] + 1;
                    }
                }

                else if (c1.G >= 64 && c1.G <= 127)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[4] = RGBColour[4] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[5] = RGBColour[5] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[6] = RGBColour[6] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[7] = RGBColour[7] + 1;
                    }

                }
                else if (c1.G >= 128 && c1.G <= 191)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[8] = RGBColour[8] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[9] = RGBColour[9] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[10] = RGBColour[10] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[11] = RGBColour[11] + 1;
                    }

                }
                else if (c1.G >= 192 && c1.G <= 255)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[12] = RGBColour[12] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[13] = RGBColour[13] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[14] = RGBColour[14] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[15] = RGBColour[15] + 1;
                    }

                }
            }

            //Second part of the red checking
            else if (c1.R >= 64 && c1.R <= 127)
            {

                if (c1.G >= 0 && c1.G <= 63)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[16] = RGBColour[16] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[17] = RGBColour[17] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[18] = RGBColour[18] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[19] = RGBColour[19] + 1;
                    }
                }

                else if (c1.G >= 64 && c1.G <= 127)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[20] = RGBColour[20] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[21] = RGBColour[21] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[22] = RGBColour[22] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[23] = RGBColour[23] + 1;
                    }

                }
                else if (c1.G >= 128 && c1.G <= 191)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[24] = RGBColour[24] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[25] = RGBColour[25] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[26] = RGBColour[26] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[27] = RGBColour[27] + 1;
                    }

                }
                else if (c1.G >= 192 && c1.G <= 255)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[28] = RGBColour[28] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[29] = RGBColour[29] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[30] = RGBColour[30] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[31] = RGBColour[31] + 1;
                    }

                }

            }

            //Third part of the red checking
            else if (c1.R >= 128 && c1.R <= 191)
            {

                if (c1.G >= 0 && c1.G <= 63)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[32] = RGBColour[32] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[33] = RGBColour[33] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[34] = RGBColour[34] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[35] = RGBColour[35] + 1;
                    }
                }

                else if (c1.G >= 64 && c1.G <= 127)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[36] = RGBColour[36] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[37] = RGBColour[37] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[38] = RGBColour[38] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[39] = RGBColour[39] + 1;
                    }

                }
                else if (c1.G >= 128 && c1.G <= 191)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[40] = RGBColour[40] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[41] = RGBColour[41] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[42] = RGBColour[42] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[43] = RGBColour[43] + 1;
                    }

                }
                else if (c1.G >= 192 && c1.G <= 255)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[44] = RGBColour[44] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[45] = RGBColour[45] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[46] = RGBColour[46] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[47] = RGBColour[47] + 1;
                    }

                }

            }

            //Fourth and last part of the red checking
            else if (c1.R >= 192 && c1.R <= 255)
            {

                if (c1.G >= 0 && c1.G <= 63)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[48] = RGBColour[48] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[49] = RGBColour[49] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[50] = RGBColour[50] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[51] = RGBColour[51] + 1;
                    }
                }

                else if (c1.G >= 64 && c1.G <= 127)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[52] = RGBColour[52] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[53] = RGBColour[53] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[54] = RGBColour[54] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[55] = RGBColour[55] + 1;
                    }

                }
                else if (c1.G >= 128 && c1.G <= 191)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[56] = RGBColour[56] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[57] = RGBColour[57] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[58] = RGBColour[58] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[59] = RGBColour[59] + 1;
                    }

                }
                else if (c1.G >= 192 && c1.G <= 255)
                {
                    if (c1.B >= 0 && c1.B <= 63)
                    {
                        RGBColour[60] = RGBColour[60] + 1;
                    }

                    else if (c1.B >= 64 && c1.B <= 127)
                    {
                        RGBColour[61] = RGBColour[61] + 1;
                    }

                    else if (c1.B >= 128 && c1.B <= 191)
                    {
                        RGBColour[62] = RGBColour[62] + 1;
                    }

                    else if (c1.B >= 192 && c1.B <= 255)
                    {
                        RGBColour[63] = RGBColour[63] + 1;
                    }

                }

            }
            
          }


        public Double CalculateHistogramComparison(Int32[] result1, Int32[] result2)
        {
            Double percent, temp, resultDouble1, resultDouble2;
            Int32 count = 64;
            temp = 0;
            percent = 0;
            for (int i = 0; i <= 63; i++)
            {

                //the check that each result is great than 100 is to determine the best percentage of results
                //as if one bis has 1 entry and the other bin had 7 this will produce an incosistent average
                //due to the fact that this is only conuting a very small percantage of pixels in the compared pictures.

                if ((result1[i] < result2[i]) && ((result1[i] >= 100) || (result2[i] >= 100)) )
                {
                    resultDouble1 = result1[i];
                    resultDouble2 = result2[i];
                    temp = (resultDouble1 / resultDouble2) * 100;
                    percent = percent + temp;
                }
                else if ((result1[i] > result2[i]) && ((result1[i] >= 100) || (result2[i] >= 100)))
                {
                    resultDouble1 = result1[i];
                    resultDouble2 = result2[i];
                    temp = (resultDouble2 / resultDouble1) * 100;
                    percent = percent + temp;
                }
                else if ((result1[i] == 0) && (result1[i] == 0))
                {
                    percent = percent + 100;                  
                }
                else if ((result1[i] == result2[i]) || (result1[i] < 100) || (result2[i] < 100))
                {
                    percent = percent + 100;
                }
                
            }

            percent = (percent / count);
            return percent;

        }

        private void btnImage1_Click(object sender, EventArgs e)
        {
            ImageDialog1.ShowDialog();

            txtImage1.Text = ImageDialog1.FileName;
        }

       
        
        //Kyle - Divide image into tiles
        public Array divide_image_into_tiles_new(Bitmap img){

            Rectangle crop_area; //this will be used for the cropping of images

            string image_filename = null; // Filename of the new image tile

            // Create random name for image tile
            string random_name = Path.GetRandomFileName(); 
            random_name = random_name.Replace(".", "");

            //This value are both just random and will be sorted out later
            int tile_size_Width = img.Width / 4; // 4 blocks across
            int tile_size_Height = img.Height / 4; // 4 blocks down 

            //Count number of tiles accross and down - Should be 4 as its set above for now
            int total_titles_wide = img.Width / tile_size_Width;
            int total_titles_high = img.Height/ tile_size_Height;

            //Current Position on the image for cropping
            int current_x = 0;
            int current_y = 0;

            //Number of image tiles created.
            int counter = 0;

            //An Array to store the tile filenamess
            string[] image_names = new string[100];

            //Create the crop area as an object
            crop_area = new Rectangle(current_x, current_y, tile_size_Width, tile_size_Height);

            //Loop through the vertical Tiles
            for (int i_height = 1; i_height < total_titles_high; i_height++)
            {
                //Loop through the horizontal Tiles
                for (int i_wigth = 1; i_wigth < total_titles_wide; i_wigth++)
                {
                    image_filename = "C:\\Documents and Settings\\Kyle\\My Documents\\Visual Studio 2010\\Projects\\csharptesting\\ImageComparison\\ImageComparison\\Sample Pictures\\temp\\" + random_name + "-" + counter + ".gif";
                    image_names[counter] = image_filename;

                    crop_area.Location = new Point(current_x, current_y);

                    Bitmap new_images = img.Clone(crop_area, img.PixelFormat);
                    new_images.Save(image_filename, System.Drawing.Imaging.ImageFormat.Gif);
                    new_images.Dispose();

                    

                    current_x += tile_size_Width;
                    counter++;
                   
                }

                current_x = 0;
                current_y += tile_size_Height;
            }


            return image_names;
        }




        private void btnCreateImageTitles_Click(object sender, EventArgs e)
        {

            Console.WriteLine("Button Clicked");
            string image1Name;
            image1Name = txtImage1.Text;


            Bitmap image1 = new Bitmap(image1Name);
            
            pictureBox1.Enabled = true;
            pictureBox1.Visible = true;
            pictureBox1.SizeMode = PictureBoxSizeMode.AutoSize;

            pictureBox1.Image = image1;
            lbl_image_path.Visible = true;

            this.Invalidate();

            foreach (string picture in divide_image_into_tiles_new(image1) )
            {

                if (picture == "" ||  picture == null)
                {
                    continue;
                }

                lbl_image_path.Text = "Image Path: " + picture;

                pictureBox1.Image = Image.FromFile(picture);
                pictureBox1.Focus();

                this.Refresh();
                this.Invalidate();

                System.Threading.Thread.Sleep(1500);

            }

        }

        private void Form1_Load(object sender, EventArgs e)
        {

        }

   
    }
}
